home *** CD-ROM | disk | FTP | other *** search
/ Mac Easy 2010 May / Mac Life Ubuntu.iso / casper / filesystem.squashfs / usr / share / ghostscript / 8.64 / Resource / Init / gs_res.ps < prev    next >
Encoding:
Text File  |  2009-04-17  |  36.6 KB  |  1,119 lines

  1. %    Copyright (C) 1994, 1996, 1997, 1998, 1999, 2000 Aladdin Enterprises.  All rights reserved.
  2. % This software is provided AS-IS with no warranty, either express or
  3. % implied.
  4. % This software is distributed under license and may not be copied,
  5. % modified or distributed except as expressly authorized under the terms
  6. % of the license contained in the file LICENSE in this distribution.
  7. % For more information about licensing, please refer to
  8. % http://www.ghostscript.com/licensing/. For information on
  9. % commercial licensing, go to http://www.artifex.com/licensing/ or
  10. % contact Artifex Software, Inc., 101 Lucas Valley Road #110,
  11. % San Rafael, CA  94903, U.S.A., +1(415)492-9861.
  12.  
  13. % $Id: gs_res.ps 8954 2008-08-08 04:22:38Z ray $
  14. % Initialization file for Level 2 resource machinery.
  15. % When this is run, systemdict is still writable,
  16. % but (almost) everything defined here goes into level2dict.
  17.  
  18. level2dict begin
  19.  
  20. (BEGIN RESOURCES) VMDEBUG
  21.  
  22. % We keep track of (global) instances with another entry in the resource
  23. % dictionary, an .Instances dictionary.  For categories with implicit
  24. % instances, the values in .Instances are the same as the keys;
  25. % for other categories, the values are [instance status size].
  26.  
  27. % Note that the dictionary that defines a resource category is stored
  28. % in global VM.  The PostScript manual says that each category must
  29. % manage global and local instances separately.  However, objects in
  30. % global VM other than systemdict can't reference objects in local VM.
  31. % This means that the resource category dictionary, which would otherwise be
  32. % the obvious place to keep track of the instances, can't be used to keep
  33. % track of local instances.  Instead, we define a dictionary in local VM
  34. % called localinstancedict, in which the key is the category name and
  35. % the value is the analogue of .Instances for local instances.
  36.  
  37. % We don't currently implement automatic resource unloading.
  38. % When and if we do, it should be hooked to the garbage collector.
  39. % However, Ed Taft of Adobe says their interpreters don't implement this
  40. % either, so we aren't going to worry about it for a while.
  41.  
  42. currentglobal false setglobal systemdict begin
  43.   /localinstancedict 5 dict
  44.   .forcedef    % localinstancedict is local, systemdict is global
  45. end true setglobal
  46. /.emptydict 0 dict readonly def
  47. setglobal
  48.  
  49. % Resource category dictionaries have the following keys (those marked with
  50. % * are optional):
  51. %    Standard, defined in the Red Book:
  52. %        Category (name)
  53. %        *InstanceType (name)
  54. %        DefineResource
  55. %            <key> <instance> DefineResource <instance>
  56. %        UndefineResource
  57. %            <key> UndefineResource -
  58. %        FindResource
  59. %            <key> FindResource <instance>
  60. %        ResourceStatus
  61. %            <key> ResourceStatus <status> <size> true
  62. %            <key> ResourceStatus false
  63. %        ResourceForAll
  64. %            <template> <proc> <scratch> ResourceForAll -
  65. %        *ResourceFileName
  66. %            <key> <scratch> ResourceFileName <filename>
  67. %    Additional, specific to our implementation:
  68. %        .Instances (dictionary)
  69. %        .LocalInstances
  70. %            - .LocalInstances <dict>
  71. %        .GetInstance
  72. %            <key> .GetInstance <instance> -true-
  73. %            <key> .GetInstance -false-
  74. %        .CheckResource
  75. %            <key> <value> .CheckResource <key> <value> <ok>
  76. %              (or may give an error if not OK)
  77. %        .DoLoadResource
  78. %            <key> .DoLoadResource <key> (may give an error)
  79. %        .LoadResource
  80. %            <key> .LoadResource - (may give an error)
  81. %        .ResourceFile
  82. %            <key> .ResourceFile <file> -true-
  83. %            <key> .ResourceFile <key> -false-
  84. %        .ResourceFileStatus
  85. %            <key> .ResourceFileStatus 2 <vmusage> -true-
  86. %            <key> .ResourceFileStatus -false-
  87. % All the above procedures expect that the top dictionary on the d-stack
  88. % is the resource dictionary.
  89.  
  90. % Define enough of the Category category so we can define other categories.
  91. % The dictionary we're about to create will become the Category
  92. % category definition dictionary.
  93.  
  94. % .findcategory and .resourceexec are only called from within the
  95. % implementation of the resource 'operators', so they don't have to worry
  96. % about cleaning up the stack if they fail (the interpreter's stack
  97. % protection machinery for pseudo-operators takes care of this).
  98. % Note that all places that look up categories must use .findcategory
  99. % so that the command in case of error will be correct rather than an
  100. % internal invocation of findresource.
  101. /.findcategory {    % <name> .findcategory -
  102.             %   (pushes the category on the dstack)
  103.     /Category .findresource begin    % note: *not* findresource
  104. } bind def
  105.  
  106. % If an error occurs within the logic of a resource operator (after operand
  107. % acquisition and checking), the Adobe interpreters report the operator name,
  108. % not the operator object, as the command in $error.  For this reason, and
  109. % this reason only, all resource operators must wrap their logic code in
  110. %    /<opername> cvx { ...logic... } .errorexec
  111.  
  112. % The Category resource signals /undefined rather than /undefinedresource,
  113. % both when referenced implicitly (to look up the category for a general
  114. % resource operation) and when it is accessed directly (/Category /xxx
  115. % findresource).  Because of this, all resource operators must use
  116. % .undefinedresource rather than signalling undefinedresource directly.
  117. /.undefinedresource {    % <command> .undefinedresource -
  118.     /Category dup load eq { /undefined } { /undefinedresource } ifelse
  119.     signaloperror
  120. } bind def
  121.  
  122. /.resourceexec {    % <key> /xxxResource .resourceexec -
  123.             %   (also pops the category from the dstack)
  124.   load exec end
  125. } bind def
  126.  
  127. % .getvminstance treats instances on disk as undefined.
  128. /.getvminstance {    % <key> .getvminstance <instance> -true-
  129.             % <key> .getvminstance -false-
  130.   .GetInstance {
  131.     dup 1 get 2 ne { true } { pop false } ifelse
  132.   } {
  133.     false
  134.   } ifelse
  135. } bind def
  136.  
  137. 20 dict begin
  138.  
  139.         % Standard entries
  140.  
  141. /Category /Category def
  142. /InstanceType /dicttype def
  143.  
  144. /DefineResource {
  145.     .CheckResource {
  146.       dup /Category 3 index cvlit .growput
  147.       dup [ exch 0 -1 ] exch
  148.       .Instances 4 2 roll put
  149.         % Make the Category dictionary read-only.  We will have to
  150.         % use .forceput / .forcedef later to replace the dummy,
  151.         % empty .Instances dictionary with the real one later.
  152.       readonly
  153.     } {
  154.       /defineresource cvx /typecheck signaloperror
  155.     } ifelse
  156. } bind def
  157. /FindResource        % (redefined below)
  158.     { .Instances exch get 0 get
  159.     } bind def
  160.  
  161.         % Additional entries
  162.  
  163. /.Instances 30 dict def
  164. .Instances /Category [currentdict 0 -1] put
  165.  
  166. /.LocalInstances 0 dict def
  167. /.GetInstance
  168.     { .Instances exch .knownget
  169.     } bind def
  170. /.CheckResource
  171.     { dup gcheck currentglobal and
  172.        { /DefineResource /FindResource /ResourceForAll /ResourceStatus
  173.          /UndefineResource }
  174.        { 2 index exch known and }
  175.       forall
  176.       not { /defineresource cvx /invalidaccess signaloperror } if
  177.       true
  178.     } bind def
  179.  
  180. .Instances end begin    % for the base case of findresource
  181.  
  182. (END CATEGORY) VMDEBUG
  183.  
  184. % Define the resource operators.  We use the "stack protection" feature of
  185. % odef to make sure the stacks are restored properly on an error.
  186. % This requires that the operators not pop anything from the stack until
  187. % they have executed their logic successfully.  We can't make this
  188. % work for resourceforall, because the procedure it executes mustn't see
  189. % the operands of resourceforall on the stack, but we can make it work for
  190. % the others.
  191.  
  192. % findresource is the only operator that needs to bind //Category.
  193. % We define its contents as a separate procedure so that .findcategory
  194. % can use it without entering another level of pseudo-operator.
  195. /.findresource {        % <key> <category> findresource <instance>
  196.     2 copy dup /Category eq
  197.       { pop //Category 0 get begin } { .findcategory } ifelse
  198.     /FindResource .resourceexec exch pop exch pop
  199. } bind
  200. end        % .Instances of Category
  201. def
  202. /findresource {
  203.     % See above re .errorexec.
  204.     1 .argindex     % also catch stackunderflow
  205.     dup type /stringtype eq { cvn } if  % for CET 23-13-04
  206.     3 1 roll exch pop
  207.     dup type /nametype ne {
  208.       /findresource .systemvar /typecheck signalerror
  209.     } if
  210.     /findresource cvx //.findresource .errorexec
  211. } odef
  212.  
  213. /defineresource {    % <key> <instance> <category> defineresource <instance>
  214.     2 .argindex 2 index 2 index    % catch stackunderflow
  215.     % See above re .errorexec.
  216.     /defineresource cvx {
  217.     .findcategory
  218.     currentdict /InstanceType known {
  219.       dup type InstanceType ne {
  220.         dup type /packedarraytype eq InstanceType /arraytype eq and
  221.         not { /defineresource cvx /typecheck signaloperror } if
  222.       } if
  223.     } if
  224.     /DefineResource .resourceexec
  225.     4 1 roll pop pop pop
  226.     } .errorexec
  227. } bind odef
  228. % We must prevent resourceforall from automatically restoring the stacks,
  229. % because we don't want the stacks restored if proc causes an error or
  230. % executes a 'stop'. On the other hand, resourceforall is defined in the
  231. % PLRM as an operator, so it must have type /operatortype.  We hack this
  232. % by taking advantage of the fact that the interpreter optimizes tail
  233. % calls, so stack protection doesn't apply to the very last token of an
  234. % operator procedure.
  235. /resourceforall1 {    % <template> <proc> <scratch> <category> resourceforall1 -
  236.     dup .findcategory
  237.     /ResourceForAll load
  238.     % Stack: <template> <proc> <scratch> <category> proc
  239.     exch pop        % pop the category
  240.     exec end
  241. } bind def
  242. /resourceforall {    % <template> <proc> <scratch> <category> resourceforall1 -
  243.     //resourceforall1 exec        % see above
  244. } bind odef
  245. /resourcestatus {    % <key> <category> resourcestatus <status> <size> true
  246.             % <key> <category> resourcestatus false
  247.   {
  248.     0 .argindex type /nametype ne {
  249.       % CET 23-26 wants typecheck here, not undefineresource that happens
  250.       % without the check.
  251.       /resourcestatus cvx /typecheck signalerror
  252.     } if
  253.     2 copy .findcategory /ResourceStatus .resourceexec
  254.     { 4 2 roll pop pop true } { pop pop false } ifelse
  255.   } stopped {
  256.     % Although resourcestatus is an operator, Adobe uses executable name
  257.     % for error reporting. CET 23-26
  258.     /resourcestatus cvx $error /errorname get signalerror
  259.   } if
  260. } bind odef
  261. /undefineresource {    % <key> <category> undefineresource -
  262.   0 .argindex type /nametype ne {
  263.     /undefinedresource cvx /typecheck signaloperror
  264.   } if
  265.   1 .argindex 1 index        % catch stackunderflow
  266.  
  267.   { .findcategory /UndefineResource .resourceexec pop pop
  268.   } stopped {
  269.     % Although undefineresource is an operator, Adobe uses executable name
  270.     % here but uses operator for the errors above. CET 23-33
  271.     /undefineresource cvx $error /errorname get signalerror
  272.   } if
  273. } bind odef
  274.  
  275. % Define the system parameters used for the Generic implementation of
  276. % ResourceFileName.
  277. systemdict begin
  278.  
  279. %     - .default_resource_dir <string>
  280. /.default_resource_dir {
  281.   /LIBPATH .systemvar {
  282.     dup .file_name_current eq {
  283.       pop
  284.     } {
  285.       (Resource) search {
  286.         exch concatstrings
  287.         exch 0 1 getinterval concatstrings exit
  288.       } {
  289.         pop
  290.       } ifelse
  291.     } ifelse
  292.   } forall
  293. } bind def
  294.  
  295. %  <path> <name> <string> .resource_dir_name <path> <name> <string>
  296. /.resource_dir_name
  297. {  systemdict 2 index .knownget {
  298.      exch pop
  299.      systemdict 1 index undef
  300.    } {
  301.      dup () ne {
  302.      .file_name_directory_separator concatstrings
  303.     } if
  304.     2 index exch false .file_name_combine not {
  305.       (Error: .default_resource_dir returned ) print exch print ( that can't combine with ) print =
  306.       /.default_resource_dir cvx /configurationerror signalerror
  307.     } if
  308.   } ifelse
  309. } bind def
  310.  
  311. currentdict /pssystemparams known not {
  312.   /pssystemparams 10 dict readonly def
  313. } if
  314. pssystemparams begin
  315.   .default_resource_dir
  316.   /FontResourceDir (Font) .resource_dir_name
  317.      readonly .forcedef    % pssys'params is r-o
  318.   /GenericResourceDir () .resource_dir_name
  319.      readonly .forcedef    % pssys'params is r-o
  320.   pop % .default_resource_dir
  321.   /GenericResourcePathSep
  322.       .file_name_separator readonly .forcedef        % pssys'params is r-o
  323.   (%diskFontResourceDir) cvn (/Resource/Font/) readonly .forcedef    % pssys'params is r-o
  324.   (%diskGenericResourceDir) cvn (/Resource/) readonly .forcedef    % pssys'params is r-o
  325. end
  326. end
  327.  
  328. % Check if GenericResourceDir presents in LIBPATH.
  329.  
  330. % The value of GenericResourceDir must end with directory separator.
  331. % We use .file_name_combine to check it. 
  332. % Comments use OpenVMS syntax, because it is the most complicated case.
  333. (x) pssystemparams /GenericResourcePathSep get
  334. (y) concatstrings concatstrings dup length              % (x]y) l1
  335. pssystemparams /GenericResourceDir get dup length exch  % (x]y) l1 l2 (dir)
  336. 3 index true .file_name_combine not {
  337.   exch
  338.   (File name ) print print ( cant combine with ) print =
  339.   /GenericResourceDir cvx /configurationerror signaloperror
  340. } if
  341. dup length                                              % (x]y) l1 l2 (dir.x]y) l
  342. 4 2 roll add                                            % (x]y) (dir.x]y) l ll
  343. ne {
  344.   (GenericResourceDir value does not end with directory separator.\n) =
  345.   /GenericResourceDir cvx /configurationerror signaloperror
  346. } if
  347. pop pop
  348.  
  349. % Define the generic algorithm for computing resource file names.
  350. /.rfnstring 8192 string def
  351. /.genericrfn        % <key> <scratch> <prefix> .genericrfn <filename>
  352.  { 3 -1 roll //.rfnstring cvs concatstrings exch copy
  353.  } bind def
  354.  
  355. % Define the Generic category.
  356.  
  357. /Generic mark
  358.  
  359.         % Standard entries
  360.  
  361. % We're still running in Level 1 mode, so dictionaries won't expand.
  362. % Leave room for the /Category entry.
  363. /Category null
  364.  
  365. % Implement the body of Generic resourceforall for local, global, and
  366. % external cases.  'args' is [template proc scratch resdict].
  367. /.enumerateresource {    % <key> [- <proc> <scratch>] .enumerateresource -
  368.   1 index type dup /stringtype eq exch /nametype eq or {
  369.     exch 1 index 2 get cvs exch
  370.   } if
  371.     % Use .setstackprotect to prevent the stacks from being restored if
  372.     % an error occurs during execution of proc.
  373.   1 get false .setstackprotect exec true .setstackprotect
  374. } bind def
  375. /.localresourceforall {        % <key> <value> <args> .localr'forall -
  376.   exch pop
  377.   2 copy 0 get .stringmatch { .enumerateresource } { pop pop } ifelse
  378. } bind def
  379. /.globalresourceforall {    % <key> <value> <args> .globalr'forall -
  380.   exch pop
  381.   2 copy 0 get .stringmatch {
  382.     dup 3 get begin .LocalInstances end 2 index known not {
  383.       .enumerateresource
  384.     } {
  385.       pop pop
  386.     } ifelse
  387.   } {
  388.     pop pop
  389.   } ifelse
  390. } bind def
  391. /.externalresourceforall {    % <filename> <len> <args> .externalr'forall -
  392.   3 1 roll 1 index length 1 index sub getinterval exch
  393.   dup 3 get begin .Instances .LocalInstances end
  394.         % Stack: key args insts localinsts
  395.   3 index known {
  396.     pop pop pop
  397.   } {
  398.     2 index known { pop pop } { .enumerateresource } ifelse
  399.   } ifelse
  400. } bind def
  401.  
  402. /DefineResource {
  403.     .CheckResource
  404.        { dup [ exch 0 -1 ]
  405.             % Stack: key value instance
  406.          currentglobal
  407.           { false setglobal 2 index UndefineResource    % remove local def if any
  408.         true setglobal
  409.         .Instances dup //.emptydict eq {
  410.           pop 3 dict
  411.             % As noted above, Category dictionaries are read-only,
  412.             % so we have to use .forcedef here.
  413.           /.Instances 1 index .forcedef    % Category dict is read-only
  414.         } if
  415.           }
  416.           { .LocalInstances dup //.emptydict eq
  417.              { pop 3 dict localinstancedict Category 2 index put
  418.          }
  419.         if
  420.           }
  421.          ifelse
  422.             % Stack: key value instance instancedict
  423.          3 index 2 index .growput
  424.             % Now make the resource value read-only.
  425.          0 2 copy get { readonly } .internalstopped pop
  426.          dup 4 1 roll put exch pop exch pop
  427.        }
  428.        { /defineresource cvx /typecheck signaloperror
  429.        }
  430.     ifelse
  431. } .bind executeonly        % executeonly to prevent access to .forcedef
  432. /UndefineResource
  433.     {  { dup 2 index .knownget
  434.           { dup 1 get 1 ge
  435.          { dup 0 null put 1 2 put pop pop }
  436.          { pop exch .undef }
  437.         ifelse
  438.           }
  439.           { pop pop
  440.           }
  441.          ifelse
  442.        }
  443.       currentglobal
  444.        { 2 copy .Instances exch exec
  445.        }
  446.       if .LocalInstances exch exec
  447.     } bind
  448. % Because of some badly designed code in Adobe's CID font downloader that
  449. % makes findresource and resourcestatus deliberately inconsistent with each
  450. % other, the default FindResource must not call ResourceStatus if there is
  451. % an instance of the desired name already defined in VM.
  452. /FindResource {
  453.     dup //null eq {
  454.           % CET 13-06 wants /typecheck for "null findencoding" but
  455.           % .knownget doesn't fail on null
  456.           /findresource cvx /typecheck signaloperror
  457.         } if
  458.     dup .getvminstance {
  459.       exch pop 0 get
  460.     } {
  461.       dup ResourceStatus {
  462.         pop 1 gt {
  463.           .DoLoadResource .getvminstance not {
  464.         /findresource cvx .undefinedresource
  465.           } if 0 get
  466.         } {
  467.           .GetInstance pop 0 get
  468.         } ifelse
  469.       } {
  470.        /findresource cvx .undefinedresource
  471.       } ifelse
  472.     } ifelse
  473. } bind
  474. % Because of some badly designed code in Adobe's CID font downloader, the
  475. % definition of ResourceStatus for Generic and Font must be the same (!).
  476. % We patch around this by using an intermediate .ResourceFileStatus procedure.
  477. /ResourceStatus {
  478.     dup .GetInstance {
  479.       exch pop dup 1 get exch 2 get true
  480.     } {
  481.       .ResourceFileStatus
  482.     } ifelse
  483. } bind
  484. /.ResourceFileStatus {
  485.     .ResourceFile { closefile 2 -1 true } { pop false } ifelse
  486. } bind
  487. /ResourceForAll {
  488.         % Construct a new procedure to hold the arguments.
  489.         % All objects constructed here must be in local VM to avoid
  490.         % a possible invalidaccess.
  491.     currentdict 4 .localvmpackedarray    % [template proc scratch resdict]
  492.         % We must pop the resource dictionary off the dict stack
  493.         % when doing the actual iteration, and restore it afterwards.
  494.     .currentglobal not {
  495.       .LocalInstances length 0 ne {
  496.         % We must do local instances, and do them first.
  497.         //.localresourceforall {exec} 0 get 3 .localvmpackedarray cvx
  498.         .LocalInstances exch {forall} 0 get 1 index 0 get
  499.         currentdict end 3 .execn begin
  500.       } if
  501.     } if
  502.         % Do global instances next.
  503.     //.globalresourceforall {exec} 0 get 3 .localvmpackedarray cvx
  504.     .Instances exch cvx {forall} 0 get 1 index 0 get
  505.     currentdict end 3 .execn begin
  506.         mark                                             % args [
  507.         Category .namestring .file_name_separator concatstrings
  508.         2 index 0 get                                    % args [ (c/) (t)
  509.         dup length 3 1 roll                              % args [ l (c/) (t)
  510.         concatstrings                                    % args [ l (c/t)
  511.     [ 
  512.       true /LIBPATH .systemvar 3 index
  513.       .generate_dir_list_templates_with_length       % args (t) [ l [(pt) Lp ...]
  514.         % also add on the Resources as specified by the GenericResourceDir
  515.           true [ currentsystemparams /GenericResourceDir get]
  516.       counttomark 1 add index .generate_dir_list_templates_with_length
  517.             % Resource files on OpenVMS require a separate template (gs:[dir.*]*)
  518.           true [ currentsystemparams /GenericResourceDir get]
  519.       counttomark 1 add index .file_name_separator (*)
  520.           concatstrings concatstrings .generate_dir_list_templates_with_length
  521.       ] exch pop
  522.     dup length 1 sub 0 exch 2 exch {                 % args [ l [] i
  523.       2 copy get                                     % args [ l [] i (pt)
  524.       exch 2 index exch 1 add get                    % args [ l [] (pt) Lp
  525.       exch                                           % args [ l [] Lp (pt)
  526.  
  527.       {                                              % args [ l [] Lp (pf)
  528.         dup length                                   % args [ l [] Lp (pf) Lpf
  529.         2 index sub                                  % args [ l [] Lp (pf) Lf
  530.         2 index exch                                 % args [ l [] Lp (pf) Lp Lf
  531.         getinterval cvn dup                          % args [ l [] Lp /n /n
  532.         5 2 roll                                     % args [ /n /n l [] Lp
  533.       } //.rfnstring filenameforall
  534.       pop                                            % args [ /n1 /n1 ... /nN /nN l []
  535.     } for                                            % args [ /n1 /n1 ... /nN /nN l []
  536.     pop pop
  537.     .dicttomark % An easy way to exclude duplicates. % args <</n/n>>
  538.       % {
  539.       { pop } 0 get
  540.           2 index 2 get { cvs 0 } aload pop 5 index
  541.           //.externalresourceforall {exec} 0 get
  542.           % }
  543.         7 .localvmpackedarray cvx
  544.         3 2 roll pop % args
  545.     { forall } 0 get
  546.       currentdict end 2 .execn begin
  547. } bind
  548. /.file_name_is_iodevice_or_absolute
  549. { {
  550.     dup length 0 gt {
  551.       dup 0 get (%) 0 get eq {
  552.         pop true exit
  553.       } if
  554.     } if
  555.     .file_name_is_absolute exit
  556.   } loop
  557. } bind def
  558. /ResourceFileName
  559.       {                                             % /in (scr)
  560.         exch //.rfnstring cvs                       % (scr) (n)
  561.             /GenericResourcePathSep getsystemparam exch % (scr) (/) (n)
  562.             Category .namestring                        % (scr) (/) (n) (c)
  563.             3 1 roll                                    % (scr) (c) (/) (n)
  564.         concatstrings concatstrings                 % (scr) (c/n)
  565.             /GenericResourceDir getsystemparam //.file_name_is_iodevice_or_absolute exec not {
  566.               /GenericResourceDir getsystemparam exch concatstrings
  567.           findlibfile
  568.           {                                         % (scr) (p/c/n) file
  569.             pop exch copy true                      % (p/c/n) true
  570.           } {                                       % (scr) (c/n)
  571.             false                                   % (scr) (c/n) false
  572.           } ifelse
  573.         } {                                         % (scr) (c/n)
  574.           false                                     % (scr) (c/n) false
  575.         } ifelse
  576.         not {                                       % (scr) (c/n)
  577.               /GenericResourceDir getsystemparam        % (scr) (c/n) (d/)
  578.               dup length exch                           % (scr) (c/n) Ld (d/)
  579.               3 index copy pop                          % (scr') (c/n) Ld
  580.               1 index length                            % (scr') (c/n) Ld Lcn
  581.               3 index 3 copy pop                        % (scr') (c/n) Ld Lcn (scr') Ld Lcn
  582.               getinterval                               % (scr') (c/n) Ld Lcn (scr[Ld:Lcn])
  583.               4 3 roll exch                             % (scr') Ld Lcn (c/n) (scr[Ld:Lcn])
  584.               copy pop                                  % (scr'') Ld Lcn
  585.               add 0 exch getinterval                    % (scr''[0:Ld+Lcn])
  586.         } if
  587.       } bind
  588.  
  589.         % Additional entries
  590.  
  591. % Unfortunately, we can't create the real .Instances dictionary now,
  592. % because if someone copies the Generic category (which pp. 95-96 of the
  593. % 2nd Edition Red Book says is legitimate), they'll wind up sharing
  594. % the .Instances.  Instead, we have to create .Instances on demand,
  595. % just like the entry in localinstancedict.
  596. % We also have to prevent anyone from creating instances of Generic itself.
  597. /.Instances //.emptydict
  598.  
  599. /.LocalInstances
  600.     { localinstancedict Category .knownget not { //.emptydict } if
  601.     } bind
  602. /.GetInstance
  603.     { currentglobal
  604.        { .Instances exch .knownget }
  605.        { .LocalInstances 1 index .knownget
  606.           { exch pop true }
  607.           { .Instances exch .knownget }
  608.          ifelse
  609.        }
  610.       ifelse
  611.     } bind
  612. /.CheckResource
  613.     { true
  614.     } bind
  615. /.vmused {
  616.         % - .vmused <usedvalue>
  617.         % usedvalue = vmstatus in global + vmstatus in local.
  618.   0 2 {
  619.     .currentglobal not .setglobal
  620.     vmstatus pop exch pop add
  621.   } repeat
  622. } bind def
  623. /.DoLoadResource {
  624.         % .LoadResource may push entries on the operand stack.
  625.         % It is an undocumented feature of Adobe implementations,
  626.         % which we must match for the sake of some badly written
  627.         % font downloading code, that such entries are popped
  628.         % automatically.
  629.     count 1 index cvlit .vmused
  630.         % Stack: key count litkey memused
  631.     {.LoadResource} 4 1 roll 4 .execn
  632.         % Stack: ... count key memused
  633.     .vmused exch sub
  634.     1 index .getvminstance not {
  635.       pop dup .undefinedresource    % didn't load
  636.     } if
  637.     dup 1 1 put
  638.     2 3 -1 roll put
  639.         % Stack: ... count key
  640.     exch count 1 sub exch sub {exch pop} repeat
  641. } bind
  642. /.LoadResource
  643.     { dup .ResourceFile
  644.        { exch pop currentglobal
  645.           { .runresource }
  646.           { true setglobal { .runresource } stopped false setglobal { stop } if }
  647.          ifelse
  648.        }
  649.        { dup .undefinedresource
  650.        }
  651.      ifelse
  652.     } bind
  653. /.ResourceFile
  654.         {
  655.           Category //.rfnstring cvs length                      % key l
  656.           dup //.rfnstring dup length 2 index sub               % key l l (buf) L-l
  657.           3 2 roll exch getinterval                             % key l ()
  658.           .file_name_directory_separator exch copy length add   % key l1
  659.           dup //.rfnstring dup length 2 index sub               % key l1 l1 (buf) L-l
  660.           3 2 roll exch getinterval                             % key l1 ()
  661.           2 index exch cvs length add                           % key l2
  662.           //.rfnstring exch 0 exch getinterval                  % key (relative_path)
  663.           .libfile {
  664.             exch pop true
  665.           } {
  666.             pop
  667.             currentdict /ResourceFileName known {
  668.           mark 1 index //.rfnstring { ResourceFileName } .internalstopped {
  669.             cleartomark false
  670.           } {
  671.             (r) { file } .internalstopped {
  672.               cleartomark false
  673.         } {
  674.               exch pop exch pop true
  675.             } ifelse
  676.           } ifelse
  677.          } {
  678.            pop false
  679.          } ifelse
  680.           } ifelse
  681.     } bind
  682.  
  683.  
  684.  
  685. .dicttomark
  686. /Category defineresource pop
  687.  
  688. % Fill in the rest of the Category category.
  689. /Category /Category findresource dup
  690. /Generic /Category findresource begin {
  691.   /FindResource /ResourceForAll /ResourceStatus /.ResourceFileStatus
  692.   /UndefineResource /ResourceFileName
  693.   /.ResourceFile /.LoadResource /.DoLoadResource
  694. } { dup load put dup } forall
  695. pop readonly pop end
  696.  
  697. (END GENERIC) VMDEBUG
  698.  
  699. % Define the fixed categories.
  700.  
  701. mark
  702.     % Non-Type categories with existing entries.
  703.  /ColorSpaceFamily
  704.    { }    % These must be deferred, because optional features may add some.
  705.  /Emulator
  706.    mark EMULATORS { cvn } forall .packtomark
  707.  /Filter
  708.    { }    % These must be deferred, because optional features may add some.
  709.  /IODevice
  710.     % Loop until the .getiodevice gets a rangecheck.
  711.    errordict /rangecheck 2 copy get
  712.    errordict /rangecheck { pop stop } put    % pop the command
  713.    mark 0 { {
  714.     dup .getiodevice dup null eq { pop } { exch } ifelse 1 add
  715.    } loop} .internalstopped
  716.    pop pop pop .packtomark
  717.    4 1 roll put
  718.    .clearerror
  719.     % Type categories listed in the Red Book.
  720.  /ColorRenderingType
  721.    { }    % These must be deferred, because optional features may add some.
  722.  /FMapType
  723.    { }    % These must be deferred, because optional features may add some.
  724.  /FontType
  725.    { }    % These must be deferred, because optional features may add some.
  726.  /FormType
  727.    { }    % These must be deferred, because optional features may add some.
  728.  /HalftoneType
  729.    { }    % These must be deferred, because optional features may add some.
  730.  /ImageType
  731.    { }    % Deferred, optional features may add some.
  732.  /PatternType
  733.    { }  % Deferred, optional features may add some.
  734.     % Type categories added since the Red Book.
  735.  /setsmoothness where {
  736.    pop /ShadingType { }    % Deferred, optional features may add some.
  737.  } if
  738. counttomark 2 idiv
  739.  { mark
  740.  
  741.         % Standard entries
  742.  
  743.         % We'd like to prohibit defineresource,
  744.         % but because optional features may add entries, we can't.
  745.         % We can at least require that the key and value match.
  746.    /DefineResource
  747.     { currentglobal not
  748.        { /defineresource cvx /invalidaccess signaloperror }
  749.        { 2 copy ne
  750.           { /defineresource cvx /rangecheck signaloperror }
  751.           { dup .Instances 4 -2 roll .growput }
  752.          ifelse
  753.        }
  754.       ifelse
  755.     } bind
  756.    /UndefineResource
  757.     { /undefineresource cvx /invalidaccess signaloperror } bind
  758.    /FindResource
  759.     { .Instances 1 index .knownget
  760.        { exch pop }
  761.        { /findresource cvx .undefinedresource }
  762.       ifelse
  763.     } bind
  764.    /ResourceStatus
  765.     { .Instances exch known { 0 0 true } { false } ifelse } bind
  766.    /ResourceForAll
  767.     /Generic .findcategory /ResourceForAll load end
  768.  
  769.         % Additional entries
  770.  
  771.    counttomark 2 add -1 roll
  772.    dup length dict dup begin exch { dup def } forall end
  773.         % We'd like to make the .Instances readonly here,
  774.         % but because optional features may add entries, we can't.
  775.    /.Instances exch
  776.    /.LocalInstances    % used by ResourceForAll
  777.     0 dict def
  778.  
  779.    .dicttomark /Category defineresource pop
  780.  } repeat pop
  781.  
  782. (END FIXED) VMDEBUG
  783.  
  784. % Define the other built-in categories.
  785.  
  786. /.definecategory    % <name> -mark- <key1> ... <valuen> .definecategory -
  787.  { counttomark 2 idiv 2 add        % .Instances, Category
  788.    /Generic /Category findresource dup maxlength 3 -1 roll add
  789.    dict .copydict begin
  790.    counttomark 2 idiv { def } repeat pop    % pop the mark
  791.    currentdict end /Category defineresource pop
  792.  } bind def
  793.  
  794. /ColorRendering mark /InstanceType /dicttype .definecategory
  795. % ColorSpace is defined below
  796. % Encoding is defined below
  797. % Font is defined below
  798. /Form mark /InstanceType /dicttype .definecategory
  799. /Halftone mark /InstanceType /dicttype .definecategory
  800. /Pattern mark /InstanceType /dicttype .definecategory
  801. /ProcSet mark /InstanceType /dicttype .definecategory
  802. % Added since the Red Book:
  803. /ControlLanguage mark /InstanceType /dicttype .definecategory
  804. /HWOptions mark /InstanceType /dicttype .definecategory
  805. /Localization mark /InstanceType /dicttype .definecategory
  806. /OutputDevice mark /InstanceType /dicttype .definecategory
  807. /PDL mark /InstanceType /dicttype .definecategory
  808. % CIDFont, CIDMap, and CMap are defined in gs_cidfn.ps
  809. % FontSet is defined in gs_cff.ps
  810. % IdiomSet is defined in gs_ll3.ps
  811. % InkParams and TrapParams are defined in gs_trap.ps
  812.  
  813. (END MISC) VMDEBUG
  814.  
  815. % Define the ColorSpace category.
  816.  
  817. /.defaultcsnames mark
  818.   /DefaultGray 0
  819.   /DefaultRGB 1
  820.   /DefaultCMYK 2
  821. .dicttomark readonly def
  822.  
  823. % The "hooks" are no-ops here, redefined in LL3.
  824. /.definedefaultcs {    % <index> <value> .definedefaultcs -
  825.   pop pop
  826. } bind def
  827. /.undefinedefaultcs {    % <index> .undefinedefaultcs -
  828.   pop
  829. } bind def
  830.  
  831. /ColorSpace mark
  832.  
  833. /InstanceType /arraytype
  834.  
  835. % We keep track of whether there are any local definitions for any of
  836. % the Default keys.  This information must get saved and restored in
  837. % parallel with the local instance dictionary, so it must be stored in
  838. % local VM.
  839. userdict /.localcsdefaults false put
  840.  
  841. /DefineResource {
  842.   2 copy /Generic /Category findresource /DefineResource get exec
  843.   exch pop
  844.   exch //.defaultcsnames exch .knownget {
  845.     1 index .definedefaultcs
  846.     currentglobal not { .userdict /.localcsdefaults true put } if
  847.   } if
  848. } bind
  849.  
  850. /UndefineResource {
  851.   dup /Generic /Category findresource /UndefineResource get exec
  852.   //.defaultcsnames 1 index .knownget {
  853.     % Stack: resname index
  854.     currentglobal {
  855.       .undefinedefaultcs pop
  856.     } {
  857.     % We removed the local definition, but there might be a global one.
  858.       exch .GetInstance {
  859.     0 get .definedefaultcs
  860.       } {
  861.     .undefinedefaultcs
  862.       } ifelse
  863.     % Recompute .localcsdefaults by scanning.  This is rarely needed.
  864.       .userdict /.localcsdefaults false //.defaultcsnames {
  865.     pop .LocalInstances exch known { pop true exit } if
  866.       } forall put
  867.     } ifelse
  868.   } {
  869.     pop
  870.   } ifelse
  871. } bind
  872.  
  873. .definecategory            % ColorSpace
  874.  
  875. % Define the Encoding category.
  876.  
  877. /Encoding mark
  878.  
  879. /InstanceType /arraytype
  880.  
  881. % Handle already-registered encodings, including lazily loaded encodings
  882. % that aren't loaded yet.
  883.  
  884. /.Instances mark
  885.   EncodingDirectory
  886.    { dup length 256 eq { [ exch readonly 0 -1 ] } { pop [null 2 -1] } ifelse
  887.    } forall
  888. .dicttomark
  889.  
  890. /.ResourceFileDict mark
  891.   EncodingDirectory
  892.    { dup length 256 eq { pop pop } { 0 get } ifelse
  893.    } forall
  894. .dicttomark
  895.  
  896. /ResourceFileName
  897.  { .ResourceFileDict 2 index .knownget
  898.     { exch copy exch pop }
  899.     { /Generic /Category findresource /ResourceFileName get exec }
  900.    ifelse
  901.  } bind
  902.  
  903. .definecategory            % Encoding
  904.  
  905. % Make placeholders in level2dict for the redefined Encoding operators,
  906. % so that they will be swapped properly when we switch language levels.
  907.  
  908. /.findencoding /.findencoding load def
  909. /findencoding /findencoding load def
  910. /.defineencoding /.defineencoding load def
  911.  
  912. (END ENCODING) VMDEBUG
  913.  
  914. % Define the Font category.
  915.  
  916. /.fontstatus {        % <fontname> .fontstatus <fontname> <found>
  917.   {        % Create a loop context just so we can exit it early.
  918.         % Check Fontmap.
  919.     Fontmap 1 index .knownget {
  920.       {
  921.     dup type /nametype eq {
  922.       .fontstatus { pop null exit } if
  923.     } {
  924.       dup type /stringtype eq {
  925.         findlibfile { closefile pop null exit } if pop
  926.       } {
  927.         % Procedure, assume success.
  928.         pop null exit
  929.       } ifelse
  930.     } ifelse
  931.       } forall dup null eq { pop true exit } if
  932.     } if
  933.         % Convert names to strings; give up on other types.
  934.     dup type /nametype eq { .namestring } if
  935.     dup type /stringtype ne { false exit } if
  936.         % Check the resource directory.
  937.     dup .fonttempstring /FontResourceDir getsystemparam .genericrfn
  938.     status {
  939.       pop pop pop pop true exit
  940.     } if
  941.         % Check for a file on the search path with the same name
  942.         % as the font.
  943.     findlibfile { closefile true exit } if
  944.         % Scan a FONTPATH directory and try again.
  945.     .scannextfontdir not { false exit } if
  946.   } loop
  947. } bind def
  948.  
  949. /Font mark
  950.  
  951. /InstanceType /dicttype
  952.  
  953. /DefineResource
  954.     { 2 copy //definefont exch pop
  955.       /Generic /Category findresource /DefineResource get exec
  956.     } bind
  957. /UndefineResource
  958.     { dup //undefinefont
  959.       /Generic /Category findresource /UndefineResource get exec
  960.     } bind
  961. /FindResource {
  962.     dup .getvminstance {
  963.       exch pop 0 get
  964.     } {
  965.       dup ResourceStatus {
  966.         pop 1 gt { .loadfontresource } { .GetInstance pop 0 get } ifelse
  967.       } {
  968.         .loadfontresource
  969.       } ifelse
  970.     } ifelse
  971. } bind
  972. /ResourceForAll {
  973.     { .scannextfontdir not { exit } if } loop
  974.     /Generic /Category findresource /ResourceForAll get exec
  975. } bind
  976. /.ResourceFileStatus {
  977.     .fontstatus { pop 2 -1 true } { pop false } ifelse
  978. } bind
  979.  
  980. /.loadfontresource {
  981.     dup vmstatus pop exch pop exch
  982.         % Hack: rebind .currentresourcefile so that all calls of
  983.         % definefont will know these are built-in fonts.
  984.     currentfile {pop //findfont exec} .execasresource  % (findfont is a procedure)
  985.     exch vmstatus pop exch pop exch sub
  986.         % stack: name font vmused
  987.         % findfont has the prerogative of not calling definefont
  988.         % in certain obscure cases of font substitution.
  989.     2 index .getvminstance {
  990.       dup 1 1 put
  991.       2 3 -1 roll put
  992.     } {
  993.       pop
  994.     } ifelse exch pop
  995. } bind
  996.  
  997. /.Instances FontDirectory length 2 mul dict
  998.  
  999. .definecategory            % Font
  1000.  
  1001. % Redefine font "operators".
  1002. /.definefontmap
  1003.  { /Font /Category findresource /.Instances get
  1004.    dup 3 index known
  1005.     { pop
  1006.     }
  1007.     { 2 index
  1008.         % Make sure we create the array in global VM.
  1009.       .currentglobal true .setglobal
  1010.       [null 2 -1] exch .setglobal
  1011.       .growput
  1012.     }
  1013.    ifelse
  1014.    //.definefontmap exec
  1015.  } bind def
  1016.  
  1017. % Make sure the old definitions are still in systemdict so that
  1018. % they will get bound properly.
  1019. systemdict begin
  1020.   /.origdefinefont /definefont load def
  1021.   /.origundefinefont /undefinefont load def
  1022.   /.origfindfont /findfont load def
  1023. end
  1024. /definefont {
  1025.   { /Font defineresource } stopped {
  1026.       /definefont cvx $error /errorname get signalerror
  1027.   } if
  1028. } bind odef
  1029. /undefinefont {
  1030.   /Font undefineresource
  1031. } bind odef
  1032. % The Red Book requires that findfont be a procedure, not an operator,
  1033. % but it still needs to restore the stacks reliably if it fails.
  1034. /.findfontop {
  1035.   { /Font findresource } stopped {
  1036.     pop /findfont $error /errorname get signalerror
  1037.   } if
  1038. } bind odef
  1039. /findfont {
  1040.   .findfontop
  1041. } bind def    % Must be a procedure, not an operator
  1042.  
  1043. % Remove initialization utilities.
  1044. currentdict /.definecategory .undef
  1045. currentdict /.emptydict .undef
  1046.  
  1047. end                % level2dict
  1048.  
  1049. % Convert deferred resources after we finally switch to Level 2.
  1050.  
  1051. /.fixresources {
  1052.     % Encoding resources
  1053.   EncodingDirectory
  1054.    { dup length 256 eq
  1055.       { /Encoding defineresource pop }
  1056.       { pop pop }
  1057.      ifelse
  1058.    } forall
  1059.   /.findencoding {
  1060.     { /Encoding findresource } stopped {
  1061.       pop /findencoding $error /errorname get signalerror
  1062.     } if
  1063.   } bind def
  1064.   /findencoding /.findencoding load def        % must be a procedure
  1065.   /.defineencoding { /Encoding defineresource pop } bind def
  1066.     % ColorRendering resources and ProcSet
  1067.   systemdict /ColorRendering .knownget {
  1068.     /ColorRendering exch /ProcSet defineresource pop
  1069.     systemdict /ColorRendering undef
  1070.     /DefaultColorRendering currentcolorrendering /ColorRendering defineresource pop
  1071.   } if
  1072.     % ColorSpace resources
  1073.   systemdict /CIEsRGB .knownget {
  1074.     /sRGB exch /ColorSpace defineresource pop
  1075.     systemdict /CIEsRGB undef
  1076.   } if
  1077.     % ColorSpaceFamily resources
  1078.   colorspacedict { pop dup /ColorSpaceFamily defineresource pop } forall
  1079.     % Filter resources
  1080.   filterdict { pop dup /Filter defineresource pop } forall
  1081.     % FontType and FMapType resources
  1082.   buildfontdict { pop dup /FontType defineresource pop } forall
  1083.   mark
  1084.     buildfontdict 0 known { 2 3 4 5 6 7 8 } if
  1085.     buildfontdict 9 known { 9 } if
  1086.   counttomark { dup /FMapType defineresource pop } repeat pop
  1087.     % FormType resources
  1088.   .formtypes { pop dup /FormType defineresource pop } forall
  1089.     % HalftoneType resources
  1090.   .halftonetypes { pop dup /HalftoneType defineresource pop } forall
  1091.     % ColorRenderingType resources
  1092.   .colorrenderingtypes {pop dup /ColorRenderingType defineresource pop} forall
  1093.     % ImageType resources
  1094.   .imagetypes { pop dup /ImageType defineresource pop } forall
  1095.     % PatternType resources
  1096.   .patterntypes { pop dup /PatternType defineresource pop } forall
  1097.     % Make the fixed resource categories immutable.
  1098.   /.shadingtypes where {
  1099.     pop .shadingtypes { pop dup /ShadingType defineresource pop } forall
  1100.   } if
  1101.   [ /ColorSpaceFamily /Emulator /Filter /IODevice /ColorRenderingType
  1102.     /FMapType /FontType /FormType /HalftoneType /ImageType /PatternType
  1103.     /.shadingtypes where { pop /ShadingType } if
  1104.   ] {
  1105.     /Category findresource
  1106.     dup /.Instances get readonly pop
  1107.     .LocalInstances readonly pop
  1108.     readonly pop
  1109.   } forall
  1110.     % clean up
  1111.   systemdict /.fixresources undef
  1112. } bind def
  1113.  
  1114. %% Replace 1 (gs_resmp.ps)
  1115. (gs_resmp.ps)  dup runlibfile VMDEBUG
  1116.